from rest_framework.authentication import SessionAuthentication
from rest_framework.permissions import IsAuthenticated, AllowAny,IsAuthenticatedOrReadOnly
from rest_framework.views import APIView
from rest_framework.response import Response
from rest_framework.pagination import PageNumberPagination

from .serializers import BlogInfoSerializer
from bloginfo.models import BlogInfo as Info
from .models import *
from utils import message



# Create your views here.
from rest_framework_jwt.authentication import JSONWebTokenAuthentication


# def __init__():

def _getUserArt(request,obj,art_id):
    '''
    获取当前用户权限下指定id可修改的文章
    :param request:
    :param obj:
    :return:
    '''
    art = request.data
    user_art = obj.objects.filter(belong=request.user.id).filter(id=art_id)
    return user_art


class _MyPagination(PageNumberPagination):
    page_size = 5  # 每页显示多少条
    page_size_query_param  = 'size'  # URL中每页显示条数的参数
    page_query_param = 'page'  # URL中页码的参数
    max_page_size = None  # 最大页码数限制

    # 指定返回格式，根据需求返回一个总页数，数据存在results字典里返回
    def get_paginated_response(self, data):
        from collections import OrderedDict
        return Response(OrderedDict([('count', self.page.paginator.count), ('results', data)]))





class BlogArticle(APIView):
    """
    文章
    """
    # authentication_classes = (JSONWebTokenAuthentication, SessionAuthentication)
    permission_classes = [IsAuthenticatedOrReadOnly]
    # 动态修改权限
    permission_classes_by_action = {'POST': [IsAuthenticated],
                                    'GET': [AllowAny],
                                    'PATCH': [IsAuthenticated],
                                    'DELETE': [IsAuthenticated]
                                    }

    # def __init__(self, *args, **kwargs):
    #     super(BlogArticle, self).__init__(*args, **kwargs)



    def get_permissions(self):
        '''
        重写get_permissions
        :return:
        '''
        try:
            '''
            使用 getattr函数 通过对象属性 ”request“ 获取到request对象  再次使用通过对象属性 ”method“ 获取请求方法
            通过列表推导式返回指定权限
            报错则返回全局权限
            '''

            req = getattr(self, 'request', None)
            return [permission() for permission in self.permission_classes_by_action[getattr(req, 'method')]]
        except KeyError:
            return [permission() for permission in self.permission_classes]

    def post(self, request):
        '''
        创建文章
        :param request:
        :return:
        '''
        user= request.user
        res = request.data
        art_title = res.get('title')
        art_cover = res.get('cover')
        art_text = res.get('text')
        if art_cover==None:
            art_cover = True


        if all([art_title,art_text]):

            obj = Article.objects.create(Title=art_title,Cover=art_cover,Text=art_text,Belong=user)
            data = {
                'code': message.ARTICLE_CREATE_OK,
                'message': message.GetErrMsg(message.ARTICLE_CREATE_OK),
                'data':{
                            'art_id':obj.id,
                            'title': obj.Title,
                            'cover': obj.Cover,
                            'text':obj.Text,
                            'user_id':user.id
                        }
                    }
            return Response(data=data, status=message.SUCCSE)




        else:
            data = {
                'code': message.ERROR_ARTICLE_CREATE,
                'message': message.GetErrMsg(message.ERROR_ARTICLE_CREATE),
                'data':res
            }


            return Response(data=data,status=message.SUCCSE)

    def get(self, request):
        '''
        获取文章
        :param request:
        :return:
        '''
        page_obj = _MyPagination()


        # 文章列表 id排序
        art_list = Article.objects.all().order_by("id")

        # 实例化查询
        page_article = page_obj.paginate_queryset(queryset=art_list,request=request,view=self)

        # 序列化返回结果
        result_serializer  = BlogInfoSerializer(page_article,many=True)


        page_result  = page_obj.get_paginated_response(result_serializer.data)

        data = {
            'code': message.ARTICLE_CREATE_DATA_OK,
            'message': message.GetErrMsg(message.ARTICLE_CREATE_DATA_OK),
            'data': page_result.data
        }

        return Response(data=data,status=message.SUCCSE)



    def delete(self, request):
        '''
        删除文章
        :param request:
        :return:
        '''

        user_art = _getUserArt(request,Article,request.data.get('id'))
        art = {}
        if user_art.exists():
            art_val = user_art.values()[0]
            for item in art_val:
                art[item] = art_val[item]



        del_art = user_art.delete()

        if del_art[0]:

            data = {
                'code': message.ARTICLE_DELETE_OK,
                'message': message.GetErrMsg(message.ARTICLE_DELETE_OK),
                'data': art
            }
            return Response(data=data,status=message.SUCCSE)
        else:
            data = {
                'code': message.ERROR_ARTICLE_DELETE,
                'message': message.GetErrMsg(message.ERROR_ARTICLE_DELETE),
                'data': art
            }
            return Response(data=data, status=message.SUCCSE)

    def patch(self, request):
        '''
        更新文章
        :param request:
        :return:
        '''
        art_id = request.query_params.get('id')
        art = request.data
        user_art = _getUserArt(request,Article,art_id).values()
        print(user_art)
        art = request.data
        title = art.get('title')
        cover= art.get('cover')
        text= art.get('text')
        # belong_id= art.get('belong')
        if user_art.exists():
            user_art.update(title=title,cover=cover,text=text)

            data = {
                'code': message.ARTICLE_UPDATE_OK,
                'message': message.GetErrMsg(message.ARTICLE_UPDATE_OK),
                'data': user_art
            }
            return Response(data=data, status=message.SUCCSE)
        data = {
            'code': message.ERROR_ARTICLE_UPDATE,
            'message': message.GetErrMsg(message.ERROR_ARTICLE_UPDATE),
            'data': user_art
        }
        return Response(data=data, status=message.SUCCSE)



class BlogCategory(APIView):
    """
    分类
    """
    permission_classes = [IsAuthenticatedOrReadOnly]
    # 动态修改权限
    permission_classes_by_action = {'POST': [IsAuthenticated],
                                    'GET': [AllowAny],
                                    'PATCH': [IsAuthenticated],
                                    'DELETE': [IsAuthenticated]
                                    }

    def _get_son(self,data):
        '''
        转换为无限树的分类结构
        :return:
        '''

        lists = []
        tree = {}
        for item in data:
            tree[item['id']] = item

        for item in data:
            if not item['belong_id']:
                lists.append(tree[item['id']])
            else:
                if 'children' not in tree[item['belong_id']]:
                    tree[item['belong_id']]['children'] = []
                tree[item['belong_id']]['children'].append(tree[item['id']])
        return lists

    def get_permissions(self):
        '''
        重写get_permissions
        :return:
        '''
        try:
            '''
            使用 getattr函数 通过对象属性 ”request“ 获取到request对象  再次使用通过对象属性 ”method“ 获取请求方法
            通过列表推导式返回指定权限
            报错则返回全局权限
            '''

            req = getattr(self, 'request', None)
            return [permission() for permission in self.permission_classes_by_action[getattr(req, 'method')]]
        except KeyError:
            return [permission() for permission in self.permission_classes]

    def post(self, request):
        '''
        新建分类
        :param request:
        :return:
        '''
        res = request.data
        res_name = res.get("name")
        res_id= res.get("id")
        if res_name:
            category = Category.objects.create(name=res_name,belong_id=res_id)
            data = {
                'code': message.CATEGORY_CREATE_DATA_OK,
                'message': message.GetErrMsg(message.CATEGORY_CREATE_DATA_OK),
                'data': {
                    'id':category.id,
                    'name':category.name,
                    'belong_id':category.belong_id
                }
            }
            return Response(data=data, status=message.SUCCSE)

        data = {
                'code': message.ERROR_CATEGORY_CREATE_DATA,
                'message': message.GetErrMsg(message.ERROR_CATEGORY_CREATE_DATA),
                'data': {
                    'name': res_name,
                    'belong_id': res_id
                }
            }

        return Response(data=data, status=message.SUCCSE)




    def get(self, request):
        '''
        获取分类
        :param request:
        :return:
        '''

        categorys = Category.objects.all().values()
        list_category = []
        if categorys.exists():
            for category in categorys:
                list_category.append(category)
            # 转换为树形结构
            tree_category = self._get_son(list_category)
            data = {
                    'code': message.CATEGORY_GET_DATA_OK,
                    'message': message.GetErrMsg(message.CATEGORY_GET_DATA_OK),
                    'data': {
                        'tree':tree_category,
                        'list':list_category
                    }
                }
            return Response(data=data, status=message.SUCCSE)
        else:
            return Response(data={'code':message.ERROR,'message':message.codeMsg(message.ERROR_CATEGORY_GET_DATA)},status=message.ERROR)


    def delete(self, request):
        '''
        删除分类
        :param request:
        :return:
        '''
        res = request.data
        category = Category.objects.filter(id=res.get('id'))
        cat = {}
        if category.exists():
            art_val = category.values()[0]
            for item in art_val:
                cat[item] = art_val[item]

        print(cat)
        del_cat = category.delete()
        if del_cat[0]:
            data = {
                'code': message.CATEGORY_DELTET_DATA_OK,
                'message': message.GetErrMsg(message.CATEGORY_DELTET_DATA_OK),
                'data': cat
            }
            return Response(data=data,status=message.SUCCSE)
        else:
            data = {
                'code': message.ERROR_CATEGORY_DELTET_DATA,
                'message': message.GetErrMsg(message.ERROR_CATEGORY_DELTET_DATA),
            }
            return Response(data=data,status=message.SUCCSE)


    def patch(self, request):
        '''
        更新分类
        :param request:
        :return:
        '''


        res = request.data
        category = Category.objects.filter(id=res.get('id')).values()

        if category.exists():
            category.update(name=res.get('name'),belong=res.get('belong'))

            data = {
                'code': message.CATEGORY_UPDATE_DATA_OK,
                'message': message.GetErrMsg(message.CATEGORY_UPDATE_DATA_OK),
                'data': category
            }
            return Response(data=data, status=message.SUCCSE)
        data = {
            'code': message.ERROR_CATEGORY_UPDATE_DATA,
            'message': message.GetErrMsg(message.ERROR_CATEGORY_UPDATE_DATA),
            'data': category
        }
        return Response(data=data, status=message.SUCCSE)


class BlogFavourite(APIView):
    """
    收藏
    """
    permission_classes = [IsAuthenticatedOrReadOnly]
    # 动态修改权限
    permission_classes_by_action = {'POST': [IsAuthenticated],
                                    'GET': [AllowAny],
                                    'PATCH': [IsAuthenticated],
                                    'DELETE': [IsAuthenticated]
                                    }

    def get_permissions(self):
        '''
        重写get_permissions
        :return:
        '''
        try:
            '''
            使用 getattr函数 通过对象属性 ”request“ 获取到request对象  再次使用通过对象属性 ”method“ 获取请求方法
            通过列表推导式返回指定权限
            报错则返回全局权限
            '''

            req = getattr(self, 'request', None)
            return [permission() for permission in self.permission_classes_by_action[getattr(req, 'method')]]
        except KeyError:
            return [permission() for permission in self.permission_classes]

    def post(self, request):
        pass

    def get(self, request):
        pass

    def delete(self, request):
        pass

    def patch(self, request):
        pass


class BlogLike(APIView):
    """
    点赞
    """
    permission_classes = [IsAuthenticatedOrReadOnly]
    # 动态修改权限
    permission_classes_by_action = {'POST':[IsAuthenticated],
                                    'GET':[AllowAny],
                                    'PATCH':[IsAuthenticated],
                                    'DELETE':[IsAuthenticated]
                                    }
    def get_permissions(self):
        '''
        重写get_permissions
        :return:
        '''
        try:
            '''
            使用 getattr函数 通过对象属性 ”request“ 获取到request对象  再次使用通过对象属性 ”method“ 获取请求方法
            通过列表推导式返回指定权限
            报错则返回全局权限
            '''

            req = getattr(self, 'request', None)
            return [permission() for permission in self.permission_classes_by_action[getattr(req, 'method')]]
        except KeyError:
            return [permission() for permission in self.permission_classes]

    def post(self,request):
        pass

    def get(self,request):
        pass

    def delete(self,request):
        pass

    def patch(self,request):
        pass


class BlogPayOrder(APIView):
    """
    打赏
    """
    permission_classes = [IsAuthenticatedOrReadOnly]
    # 动态修改权限
    permission_classes_by_action = {'POST': [IsAuthenticated],
                                    'GET': [AllowAny],
                                    'PATCH': [IsAuthenticated],
                                    'DELETE': [IsAuthenticated]
                                    }

    def get_permissions(self):
        '''
        重写get_permissions
        :return:
        '''
        try:
            '''
            使用 getattr函数 通过对象属性 ”request“ 获取到request对象  再次使用通过对象属性 ”method“ 获取请求方法
            通过列表推导式返回指定权限
            报错则返回全局权限
            '''

            req = getattr(self, 'request', None)
            return [permission() for permission in self.permission_classes_by_action[getattr(req, 'method')]]
        except KeyError:
            return [permission() for permission in self.permission_classes]

    def post(self, request):
        pass

    def get(self, request):
        pass

    def delete(self, request):
        pass

    def patch(self, request):
        pass


class BlogInfo(APIView):
    '''
    通过get方法获取博客信息
    通过post方法修改博客信息

    '''
    authentication_classes = (JSONWebTokenAuthentication, SessionAuthentication)
    permission_classes = [IsAuthenticatedOrReadOnly]
    # 动态修改权限
    permission_classes_by_action = {'POST':[IsAuthenticated],
                                    'GET':[AllowAny],
                                    'PATCH':[IsAuthenticated],
                                    }



    def _blog_info(self):
        '''
        内部获取info 方法
        :return:
        '''
        bloginfo = Info.objects.values()
        blog_info = {}
        if bloginfo.exists():

            blog_info['data'] = bloginfo
        else:
            blog_info['data'] = False
        return blog_info




    def get_permissions(self):
        '''
        重写get_permissions
        :return:
        '''
        try:
            '''
            使用 getattr函数 通过对象属性 ”request“ 获取到request对象  再次使用通过对象属性 ”method“ 获取请求方法
            通过列表推导式返回指定权限
            报错则返回全局权限
            '''

            req = getattr(self, 'request', None)
            return [permission() for permission in self.permission_classes_by_action[getattr(req, 'method')]]
        except KeyError:
            return [permission() for permission in self.permission_classes]

    def get(self,request):
        '''
        此接口可能随时删除
        Unsafe interface

        :param request:
        :return data:
        '''

        user_id = request.user.id
        user = UserInfo.objects.filter(id=user_id).values()
        users = {}



        if user.exists():
            for key in user.first():
                users[key] = user.first()[key]


        else:
            users["exists"] = False



        blog_info = self._blog_info()
        data = {
            'code': message.USER_SELF_INFO_DETAILED_OK,
            'message': message.GetErrMsg(message.USER_SELF_INFO_DETAILED_OK),
            'data': {
                'user':users,
                'blog_info':blog_info
            }
        }

        return Response(data=data,status=message.SUCCSE)
    # 更新数据 patch不幂等
    def patch(self,request):
        '''
        :param request:
        :return data:
        '''
        res = request.data
        res_id = res.get("id")
        res_title = res.get("title")
        print(res)

        # 如果有数组里面的参数 真
        if all([res_id,res_title]):
            info = Info.objects.all().filter(id=res_id).values()
            info.update(Title=res_title)
            data = {
                'code': message.BLOG_INFO_EDIT_OK,
                'message': message.GetErrMsg(message.BLOG_INFO_EDIT_OK),
                'data': info
            }
            return Response(data=data, status=message.SUCCSE)
        else:

            msg = "{}或{}".format(message.GetErrMsg(message.ERROR_PARAM_IS_BLANK),message.GetErrMsg(message.ERROR_PARAM_IS_INVALID))
            data = {
                'code': message.ERROR_PARAM_IS_BLANK,
                'message': msg,
                'data': res
            }
            return Response(data=data, status=message.SUCCSE)









